package com.captain.lc.数组;

import java.util.HashMap;
import java.util.Map;

/**
 * Des:
 *
 * @author XL
 * @Date 2021/12/8 8:59
 */
public class 有效的数独 {

    public boolean isValidSudoku(char[][] board) {
        for (int i = 0; i < 9; i++) {
            if (!isPassRow(board[i])) {
                return false;
            }
        }
        //2.检查每一列
        for (int i = 0; i < 9; i++) {
            if (!isPassLine(i, board)) {
                return false;
            }
        }
        //3.判断每一个小格子
        for (int i = 0; i < 9; i += 3) {
            //内循环定义列数,一次三列
            for (int j = 0; j < 9; j += 3) {
                if (!small(i, j, board)) {
                    return false;
                }
            }
        }
        return true;
    }


    /**
     * des:
     * 检查每一行数据
     *
     * @param chars 行数据
     * @return {@link boolean }
     * @author captain
     * @date 2021/12/8 13:47
     */
    private boolean isPassRow(char[] chars) {
        Map<Character, Integer> checkMap = new HashMap<>();
        for (char c : chars) {
            if (c != '.') {
                //如果当前值已经存在
                if (checkMap.getOrDefault(c, 0) != 0) {
                    return false;
                }
                checkMap.put(c, 1);
            }
        }
        return true;
    }

    private boolean isPassLine(int cole, char[][] board) {
        HashMap<Character, Integer> checkMap = new HashMap<>();
        for (char[] chars : board) {
            char c = chars[cole];
            if (c != '.') {
                if (checkMap.getOrDefault(c, 0) != 0) {
                    return false;
                }
                checkMap.put(c, 1);
            }
        }
        return true;
    }

    private boolean small(int row, int col, char[][] board) {
        HashMap<Character, Integer> map = new HashMap<>();
        for (int i = 0; i < 3; i++) {
            for (int j = 0; j < 3; j++) {
                int rown = row + i;
                int coln = col + j;
                char c = board[rown][coln];
                if (c != '.') {
                    if (map.getOrDefault(c, 0) != 0) {
                        return false;
                    }
                    map.put(c, 1);
                }
            }
        }
        return true;
    }
}
